﻿using Volo.Abp.Domain;
using System;
using System.Collections.Generic;
using System.Linq;
using System.Text;
using Volo.Abp;

namespace Volo.Abp.Domain.Shared
{
    public static class UrlParamListExtensions
    {
        /// <summary>
        /// 尝试获取string参数
        /// </summary>
        /// <param name="list"></param>
        /// <param name="key"></param>
        /// <param name="val"></param>
        /// <returns></returns>
        public static bool TryGetString(this List<UrlParams> list, string key, out string val)
        {
            val = default;
            var parvallist = list.FirstOrDefault(e => e.Key.Equals(key, StringComparison.InvariantCultureIgnoreCase));
            if (parvallist == null)
            {
                return false;
            }
            if (parvallist.Values == null || parvallist.Values.Count < 1 || parvallist.Values[0].IsNullOrEmpty())
            {
                return false;
            }
            val = parvallist.Values[0];
            return true;
        }

        /// <summary>
        /// 尝试获取string参数
        /// </summary>
        /// <param name="list"></param>
        /// <param name="key"></param>
        /// <param name="val"></param>
        /// <returns></returns>
        public static bool TryGetKeyword(this List<UrlParams> list, out string keyword)
        {
            keyword = default;
            var parvallist = list.FirstOrDefault(e => e.Key.Equals("keyword", StringComparison.InvariantCultureIgnoreCase));
            if (parvallist == null)
            {
                return false;
            }
            if (parvallist.Values == null || parvallist.Values.Count < 1 || parvallist.Values[0].IsNullOrEmpty())
            {
                return false;
            }
            keyword = parvallist.Values[0];
            return true;
        }

        /// <summary>
        /// 尝试获取int参数
        /// </summary>
        /// <param name="list"></param>
        /// <param name="key"></param>
        /// <param name="val"></param>
        /// <returns></returns>
        public static bool TryGetInt(this List<UrlParams> list, string key, out int val)
        {
            val = default;
            var parvallist = list.FirstOrDefault(e => e.Key.Equals(key, StringComparison.InvariantCultureIgnoreCase));
            if (parvallist == null)
            {
                return false;
            }
            if (parvallist.Values == null || parvallist.Values.Count < 1 || parvallist.Values[0].IsNullOrEmpty())
            {
                return false;
            }
            return int.TryParse(parvallist.Values[0], out val);
        }

        /// <summary>
        /// 尝试获取int参数
        /// </summary>
        /// <param name="list"></param>
        /// <param name="key"></param>
        /// <param name="val"></param>
        /// <returns></returns>
        public static bool TryGetDouble(this List<UrlParams> list, string key, out double val)
        {
            val = default;
            var parvallist = list.FirstOrDefault(e => e.Key.Equals(key, StringComparison.InvariantCultureIgnoreCase));
            if (parvallist == null)
            {
                return false;
            }
            if (parvallist.Values == null || parvallist.Values.Count < 1 || parvallist.Values[0].IsNullOrEmpty())
            {
                return false;
            }
            return double.TryParse(parvallist.Values[0], out val);
        }

        /// <summary>
        /// 尝试获取 decimal 参数
        /// </summary>
        /// <param name="list"></param>
        /// <param name="key"></param>
        /// <param name="val"></param>
        /// <returns></returns>
        public static bool TryGetDecimal(this List<UrlParams> list, string key, out decimal val)
        {
            val = default;
            var parvallist = list.FirstOrDefault(e => e.Key.Equals(key, StringComparison.InvariantCultureIgnoreCase));
            if (parvallist == null)
            {
                return false;
            }
            if (parvallist.Values == null || parvallist.Values.Count < 1 || parvallist.Values[0].IsNullOrEmpty())
            {
                return false;
            }
            return decimal.TryParse(parvallist.Values[0], out val);
        }

        /// <summary>
        /// 尝试获取Guid参数
        /// </summary>
        /// <param name="list"></param>
        /// <param name="key"></param>
        /// <param name="val"></param>
        /// <returns></returns>
        public static bool TryGetGuid(this List<UrlParams> list, string key, out string val)
        {
            val = default;
            var parvallist = list.FirstOrDefault(e => e.Key.Equals(key, StringComparison.InvariantCultureIgnoreCase));
            if (parvallist == null)
            {
                return false;
            }
            if (parvallist.Values == null || parvallist.Values.Count < 1 || parvallist.Values[0].IsNullOrEmpty())
            {
                return false;
            }
            if (Guid.TryParse(parvallist.Values[0], out Guid guidVal) == false)
            {
                return false;
            }
            val = guidVal.ToString();
            return true;
        }
        /// <summary>
        /// 尝试获取Guid参数
        /// </summary>
        /// <param name="list"></param>
        /// <param name="key"></param>
        /// <param name="val"></param>
        /// <returns></returns>
        public static bool TryGetGuid(this List<UrlParams> list, string key, out Guid val)
        {
            val = default;
            var parvallist = list.FirstOrDefault(e => e.Key.Equals(key, StringComparison.InvariantCultureIgnoreCase));
            if (parvallist == null)
            {
                return false;
            }
            if (parvallist.Values == null || parvallist.Values.Count < 1 || parvallist.Values[0].IsNullOrEmpty())
            {
                return false;
            }
            if (Guid.TryParse(parvallist.Values[0], out Guid guidVal) == false)
            {
                return false;
            }
            val = guidVal;
            return true;
        }

        /// <summary>
        /// 尝试获取datetime参数
        /// </summary>
        /// <param name="list"></param>
        /// <param name="key"></param>
        /// <param name="val"></param>
        /// <returns></returns>
        public static bool TryGetDateTime(this List<UrlParams> list, string key, out DateTime val)
        {
            val = default;
            var parvallist = list.FirstOrDefault(e => e.Key.Equals(key, StringComparison.InvariantCultureIgnoreCase));
            if (parvallist == null)
            {
                return false;
            }
            if (parvallist.Values == null || parvallist.Values.Count < 1 || parvallist.Values[0].IsNullOrEmpty())
            {
                return false;
            }
            return DateTime.TryParse(parvallist.Values[0], out val);
        }


        /// <summary>
        /// 尝试获取分页参数
        /// </summary>
        /// <param name="list"></param>
        /// <returns></returns>
        public static PageDTO TryGetPageParams(this List<UrlParams> list)
        {
            PageDTO page = null;
            var parvallist = list.FirstOrDefault(e => e.Key.Equals("pageindex", StringComparison.InvariantCultureIgnoreCase));
            if (parvallist == null)
            {
                return null;
            }
            if (int.TryParse(parvallist.Values[0], out int outIndex) == false)
            {
                outIndex = 1;
            }
            parvallist = list.FirstOrDefault(e => e.Key.Equals("pagedatacount", StringComparison.InvariantCultureIgnoreCase));
            if (parvallist == null || int.TryParse(parvallist.Values[0], out int outdataCount) == false)
            {
                outdataCount = 10;
            }
            page = new PageDTO
            {
                PageIndex = outIndex,
                PageDataCount = outdataCount,
            };
            return page;
        }


        /// <summary>
        /// 尝试获取分页参数
        /// </summary>
        /// <param name="list"></param>
        /// <returns></returns>
        public static string Remove(this List<UrlParams> list, string key)
        {
            var item = list.FirstOrDefault(e => e.Key.Equals(key, StringComparison.CurrentCultureIgnoreCase));
            if (item != null)
            {
                list.Remove(item);
                return item.Values.FirstOrDefault();
            }
            return null;
        }
        /// <summary>
        /// 尝试获取分页参数
        /// </summary>
        /// <param name="list"></param>
        /// <returns></returns>
        public static void Set(this List<UrlParams> list, string key, object value)
        {
            var item = list.FirstOrDefault(e => e.Key.Equals(key, StringComparison.CurrentCultureIgnoreCase));
            if (item != null)
            {
                item.Values = new List<string>() { value.ToString() };
            }
            item = new UrlParams
            {
                Key = key,
                Values = new List<string> { value.ToString() }
            };
            list.Add(item);
        }

        /// <summary>
        /// 尝试获取分页参数
        /// </summary>
        /// <param name="list"></param>
        /// <returns></returns>
        public static bool TryGetListParams<T>(this List<UrlParams> list, string key, out List<T> values)
        {
            var keyValue = list.FirstOrDefault(e => e.Key.Equals(key, StringComparison.InvariantCultureIgnoreCase));
            values = null;
            if (keyValue == null || keyValue.Values.Count < 1 || keyValue.Values.ElementAt(0).IsNullOrEmpty())
            {
                return false;
            }
            var resultStringList = keyValue.Values.ElementAt(0).Replace("，", ",").Split(",");
            values = resultStringList.Select(e => (T)Convert.ChangeType(e, typeof(T))).ToList();

            return true;
        }


        public static void CheckKey(this List<UrlParams> list, string key)
        {
            var keyValue = list.FirstOrDefault(e => e.Key.Equals(key, StringComparison.InvariantCultureIgnoreCase));
            if (keyValue == null|| keyValue.Values == null|| keyValue.Values[0].IsNullOrEmpty()) throw new UserFriendlyException($"参数{key}必传");
        }


        /// <summary>
        /// 尝试获取string参数
        /// </summary>
        /// <param name="list"></param>
        /// <param name="key"></param>
        /// <param name="val"></param>
        /// <returns></returns>
        public static string GetString(this List<UrlParams> list, string key)
        {
            string val = default;
            var parvallist = list.FirstOrDefault(e => e.Key.Equals(key, StringComparison.InvariantCultureIgnoreCase));
            list.CheckKey(key);
            val = parvallist.Values[0];
            return val;
        }

        /// <summary>
        /// 尝试获取int参数
        /// </summary>
        /// <param name="list"></param>
        /// <param name="key"></param>
        /// <param name="val"></param>
        /// <returns></returns>
        public static int GetInt(this List<UrlParams> list, string key)
        {
            var parvallist = list.FirstOrDefault(e => e.Key.Equals(key, StringComparison.InvariantCultureIgnoreCase));
            list.CheckKey(key);
            if (int.TryParse(parvallist.Values[0], out int val)==false)
            {
                throw new UserFriendlyException($"参数{key}的值不合法");
            }
            return val;
        }

        /// <summary>
        /// 尝试获取int参数
        /// </summary>
        /// <param name="list"></param>
        /// <param name="key"></param>
        /// <param name="val"></param>
        /// <returns></returns>
        public static double GetDouble(this List<UrlParams> list, string key)
        {
            var parvallist = list.FirstOrDefault(e => e.Key.Equals(key, StringComparison.InvariantCultureIgnoreCase));
            list.CheckKey(key);
            if (double.TryParse(parvallist.Values[0], out double val)==false)
            {
                throw new UserFriendlyException($"参数{key}的值不合法");
            }
            return val;
        }

        /// <summary>
        /// 尝试获取 decimal 参数
        /// </summary>
        /// <param name="list"></param>
        /// <param name="key"></param>
        /// <param name="val"></param>
        /// <returns></returns>
        public static decimal GetDecimal(this List<UrlParams> list, string key)
        {
            var parvallist = list.FirstOrDefault(e => e.Key.Equals(key, StringComparison.InvariantCultureIgnoreCase));
            list.CheckKey(key);
            if (decimal.TryParse(parvallist.Values[0], out decimal val) == false)
            {
                throw new UserFriendlyException($"参数{key}的值不合法");
            }
            return val;
        }

        /// <summary>
        /// 尝试获取Guid参数
        /// </summary>
        /// <param name="list"></param>
        /// <param name="key"></param>
        /// <param name="val"></param>
        /// <returns></returns>
        public static Guid GetGuid(this List<UrlParams> list, string key)
        {
            var parvallist = list.FirstOrDefault(e => e.Key.Equals(key, StringComparison.InvariantCultureIgnoreCase));

            list.CheckKey(key);
            if (Guid.TryParse(parvallist.Values[0], out Guid val) == false)
            {
                throw new UserFriendlyException($"参数{key}的值不合法");
            }
            return val;
        }

        /// <summary>
        /// 尝试获取datetime参数
        /// </summary>
        /// <param name="list"></param>
        /// <param name="key"></param>
        /// <param name="val"></param>
        /// <returns></returns>
        public static DateTime TryGetDateTime(this List<UrlParams> list, string key)
        {
            var parvallist = list.FirstOrDefault(e => e.Key.Equals(key, StringComparison.InvariantCultureIgnoreCase));

            list.CheckKey(key);
            if (DateTime.TryParse(parvallist.Values[0], out DateTime val) == false)
            {
                throw new UserFriendlyException($"参数{key}的值不合法");
            }
            return val;
        }
    }
}
